package com.passioneffect.display {
	import flash.display.Bitmap;
	import flash.display.BitmapData;
	import flash.display.Graphics;
	import flash.display.Loader;
	import flash.display.LoaderInfo;
	import flash.display.MovieClip;
	import flash.display.Sprite;
	import flash.events.Event;
	import flash.events.ProgressEvent;
	import flash.net.URLRequest;
	import flash.utils.getDefinitionByName;
	
	import com.passioneffect.contentmcs.AbstractPreloader;	

	/**
	 * @author Passion Effect
	 */
	 
	/*events:
	 * 
	 * Event.OPEN
	 * Event.INIT
	 * Event.COMPLETE
	 * ProgressEvent.PROGRESS
	 *  
	 */

	public class ImageLoader extends MovieClip {
		private var _url : String = "";
		private var preloader : MovieClip;
		private var loader : Loader;
		private var loaded : Boolean;

		public var compWidth : Number = 0;
		public var compHeight : Number = 0;
		private var funcs : Array = [];
		public var autoScale : Boolean = false;
		public var autoSize:Boolean=true;
		
		private var _initHandler:Function;
		private var bitmapData:BitmapData;
		private var bitmap:Bitmap;
		
		public var preloaderColor:Number=0x000000;
		public var preloaderStroke:Number=3;
		public var preloaderRadius:Number=20;
		public var preloaderSpeed:Number=0.02;
		
		private var bg:Sprite;
		
		public function ImageLoader(preloader:AbstractPreloader=null,compWidth:Number=NaN,compHeight:Number=NaN) {
			stop();
			this.preloader=preloader;
			if(isNaN(compWidth))this.compWidth = this.width;else this.compWidth=compWidth;
			if(isNaN(compHeight))this.compHeight= this.height;else this.compHeight=compHeight;
			
			if(numChildren>0)removeChildAt(0);
			
			this.scaleX = this.scaleY = 1;
			//youtube id
			//init loader
			loader=new Loader();
			loader.contentLoaderInfo.addEventListener(Event.COMPLETE,completeHandler);
			loader.contentLoaderInfo.addEventListener(Event.INIT,initHandler);
			loader.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS,progressHandler);
			
			loader.contentLoaderInfo.addEventListener(Event.OPEN, openHandler);
			addChild(loader);
			doLater(init);
			
			drawPlaceHolder();
		}
		
		private function drawPlaceHolder() : void {
			bg=new Sprite();
			var g:Graphics=bg.graphics;
			
			g.lineStyle();
			g.beginFill(0x000000,0);
			g.drawRect(0, 0, compWidth, compHeight);
			g.endFill();
			addChild(bg);
		}

		private function initHandler(event : Event) : void {
			loaded = true;

			var tLoader:Loader=LoaderInfo(event.target).loader;
			var url:String=LoaderInfo(event.target).url;
			
			
			//scale image
			if(autoScale) {
				tLoader.scaleX = tLoader.scaleY = 1;
				if(tLoader.width - compWidth > tLoader.height - compHeight) {
					//follow width
					tLoader.scaleX = tLoader.scaleY = compWidth / tLoader.width;
				}else {
					tLoader.scaleX = tLoader.scaleY = compHeight / tLoader.height;
				}
			}else if(autoSize){
				setSize(tLoader.width,tLoader.height);
			}
			
			
			bitmapData=new BitmapData(compWidth,compHeight,true,0x000000);
			bitmapData.draw(loader);
			bitmap=new Bitmap(bitmapData);
			bitmap.smoothing=true;
			addChild(bitmap);
			
			loader.visible=false;
			loader=null;
			//dispatchEvent(event);
			dispatchEvent(new Event(Event.INIT));
			
			if(_initHandler!=null){
				this._initHandler();
			}
			
			removeChild(bg);
			bg=null;
		}
		
		
		
		public function getLoader():Loader{
			return loader;
		}
		
		public function setSize(w:Number,h:Number):void{
			compWidth=w;
			compHeight=h;
			if(preloader){
				preloader.onStart(w,h);
			}
		}
		
		private function completeHandler(event : Event) : void {
			//remove preloader
			preloader.onComplete();
			
			
			dispatchEvent(new Event(Event.COMPLETE));
		}
		
		private function progressHandler(event : ProgressEvent) : void {
			//update preloader
			//preloader.loadProgress(event.bytesLoaded, event.bytesTotal);
			dispatchEvent(event);
		}

		private function openHandler(event : Event) : void {
			
			dispatchEvent(event);
		}

		private function validate(evt : Event) : void {
			for each(var func:Function in funcs) {
				func.apply(this);
			}
			funcs = [];
			this.removeEventListener(Event.ENTER_FRAME, validate);
		}

		protected function doLater(func : Function) : void {
			for(var i:String in funcs) {
				if(funcs[i] == func) {
					return;
				}
			}
			funcs.push(func);
			this.addEventListener(Event.ENTER_FRAME, validate);
		}

		private function init() : void {
			if(_url != "") {
				load(_url);
			}
		}
		
		public function load(url : String,_initHandler : Function = null) : void {
			if(loaded)return;
			
			if(preloader==null){
				var def : Class = Class(getDefinitionByName("Preloader_ImageLoader"));
				preloader = new def();
			}
			addChild(preloader);
			
			loader.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS,preloader.progressHandler);
			loader.load(new URLRequest(url));
			
			preloader.onStart(compWidth, compHeight);
			
			this._initHandler=_initHandler;
		}
		
		public function destroy():void{
			if(!loader)return;
			loader.contentLoaderInfo.removeEventListener(Event.COMPLETE,completeHandler);
			loader.contentLoaderInfo.removeEventListener(Event.INIT,initHandler);
			loader.contentLoaderInfo.removeEventListener(ProgressEvent.PROGRESS,progressHandler);
			loader.contentLoaderInfo.removeEventListener(ProgressEvent.PROGRESS,preloader.progressHandler);
			
		}
		
		public function get source() : String {
			return _url;
		}

		public function set source(url : String) : void {
			_url = url;
		}
		
	}
}
